
package com.android.volley.toolbox.ex;

import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.HashMap;
import java.util.Map;

import com.dg.acb.utils.NBResponse;

import com.android.volley.AuthFailureError;
import com.android.volley.NetworkResponse;
import com.android.volley.Request;
import com.android.volley.Response;
import com.android.volley.VolleyLog;
import com.android.volley.Response.ErrorListener;
import com.android.volley.Response.Listener;
import com.android.volley.http.HttpEntity;
import com.android.volley.http.HttpResponse;
import com.android.volley.toolbox.HttpHeaderParser;

public class DownLoadRequest extends Request<NBResponse> {
    private Map<String, String> mHeaders = new HashMap<String, String>();

    private final Listener<NBResponse> mListener;

    private File mFile;

    /**
     * Creates a new POST request.
     * 
     * @param url URL to fetch the string at
     * @param multi
     * @param listener Listener to receive the String response
     * @param errorListener Error listener, or null to ignore errors
     */
    public DownLoadRequest(String url, String filePath,
            Listener<NBResponse> listener, ErrorListener errorListener) {
        super(Method.GET, url, errorListener);
        mFile = new File(filePath);
        mListener = listener;
    }

    public void addHeader(String key, String value) {
        mHeaders.put(key, value);
    }

    @Override
    public Map<String, String> getHeaders() throws AuthFailureError {
        return mHeaders;
    }

    @Override
    public boolean isRequestHttpResponse() {
        return true;
    }

    @Override
    protected void deliverResponse(NBResponse response) {
        if (mListener != null) {
            mListener.onResponse(response);
        }
    }

    @Override
    protected Response<NBResponse> parseNetworkResponse(NetworkResponse response) {
        if (!handlerNetworkResponse(response)) {
            return Response.success(new NBResponse(-1, "unknow"),
                    HttpHeaderParser.parseCacheHeaders(response));
        }
        return Response.success(new NBResponse(0, null),
                HttpHeaderParser.parseCacheHeaders(response));
    }

    private boolean handlerNetworkResponse(NetworkResponse response) {
         HttpResponse httpResponse = response.httpResponse;
        if (httpResponse != null && httpResponse.getEntity() != null) {
            return entityToBytes(httpResponse.getEntity());
        }
        return false;
    }

    /** Reads the contents of HttpEntity into a byte[]. */
    private boolean entityToBytes(HttpEntity httpEntity) {
        FileOutputStream fileOutStream = null;
        try {
            InputStream in = httpEntity.getContent();
            if (in == null) {
                return false;
            }
            File dir = mFile.getParentFile();
            if (!dir.exists()) {
                dir.mkdirs();
            }
            fileOutStream = new FileOutputStream(mFile);
            byte[] buffer = new byte[1024];
            int count;
            while ((count = in.read(buffer)) != -1) {
                fileOutStream.write(buffer, 0, count);
            }
            fileOutStream.flush();
            return true;
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (IllegalStateException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            try {
                // Close the InputStream and release the resources by
                // "consuming the content".
                httpEntity.consumeContent();
                if (fileOutStream != null) {
                    fileOutStream.close();
                }
            } catch (IOException e) {
                // This can happen if there was an exception above that left the
                // entity in
                // an invalid state.
                VolleyLog.v("Error occured when calling consumingContent");
            }
        }
        return false;
    }
}
